module Tablero where

import Char
import Maybe

data Color = Blanca | Negra deriving (Show, Eq)
data Ficha = Simple Color | Reina Color deriving (Show, Eq)
type Posicion = (Char, Int)
data Tablero = T (Posicion -> Maybe Ficha)
data Direccion = TL | TR | BR | BL deriving (Eq, Ord, Show)

---- Funciones de regalo ----

tableroInicial :: Tablero
tableroInicial = T f
  where
	f (i,j)
	  | j `elem` [1..3] && negro = Just (Simple Blanca)
	  | j `elem` [6..8] && negro = Just (Simple Negra)
	  | otherwise = Nothing
	  where negro = (ord i - ord 'a' + j) `mod` 2 /= 0

instance Show Tablero where
  show (T tablero) = 
      "   a b c d e f g h  \n" ++
      "  ----------------- \n" ++
      concatMap showFil [8,7..1] ++
      "  ----------------- \n" ++
      "   a b c d e f g h  \n"
    where
      showFil fil = show fil ++ " " ++
                    concatMap (showCol fil) ['a'..'h'] ++ "| " ++
                    show fil ++ "\n"
      showCol fil col = "|" ++ p (tablero (col,fil))
      p Nothing = " "
      p (Just (Simple Blanca)) = "b"
      p (Just (Reina Blanca)) = "B"
      p (Just (Simple Negra)) = "n"
      p (Just (Reina Negra)) = "N"

---- Ejercicios ----

sonIguales::Tablero->Tablero->Bool
sonIguales (T f1) (T f2) = evaluanLoMismoParaTodoPunto f1 f2 ps
        where  ps = [ (c,i) | i <-[1..8], c<-['a'..'h']]

evaluanLoMismoParaTodoPunto :: (Posicion -> Maybe Ficha) -> (Posicion -> Maybe Ficha) -> [Posicion] -> Bool
evaluanLoMismoParaTodoPunto f1 f2 ps =  foldr (&&) True ( map ( aux f1 f2 ) ps )

--Version con Recursion Explicita
--evaluanLoMismoParaTodoPunto f1 f2 []            = True
--evaluanLoMismoParaTodoPunto f1 f2 (p:ps)        = (f1 p == f2 p) && evaluanLoMismoParaTodoPunto f1 f2 ps

aux :: (Posicion -> Maybe Ficha) -> (Posicion -> Maybe Ficha)-> Posicion -> Bool
aux f1 f2 p = ( f1 p == f2 p)

instance Eq Tablero where 
       t1 == t2 = sonIguales t1 t2

      
-- Ejercicio 1
vacio :: Tablero
vacio =  T f
  where	f p  = Nothing --para cualquier x y, es Nothing, si me pasan fruta no me importa
	
	
-- Ejercicio 2
contenido :: Posicion -> Tablero -> Maybe Ficha
contenido p (T f)  = f p   -- evalua en las pos la f del tablero

poner :: Ficha -> Posicion -> Tablero -> Tablero
--crea un tablero en el que la funcion de contenido es la misma excepto que devuelve (Just ficha) en pos
poner ficha pos (T f) = T f2
	where f2 p | p==pos = Just ficha
	           | otherwise = f p

sacar :: Posicion -> Tablero -> Tablero
--crea un tablero en el que la funcion de contenido es la misma excepto que devuelve Nothing en pos
sacar pos (T f) = T f2
	where f2 p | p==pos = Nothing
	           | otherwise = f p
